<?php
/**
 * @package site
 */
class OrderPackage extends DataObject implements PermissionProvider {
    private static $singular_name = "Order Package";
    private static $plural_name = "Order Packages";

    private static $template = 'OrderPackageTemplate';

    private static $db = array(
        'Type' => 'Varchar(100)',
        'Title' => 'Varchar(250)',
        'Price' => 'Currency',
        'BV' => 'Int',
        'Status' => "Dropdown('OrderPackageStatusList')",
        'PaidDate' => 'Datetime',
        'VoidedDate' => 'Datetime',
        'Remark' => 'Varchar(250)'
    );

    private static $has_one = array(
        'Batch' => 'BonusBatch',
        'Package' => 'Package',
        'UpgradeGroup' => 'Group',
        'BillingAddress' => 'PackageBillingAddress',
        'PaymentReceipt' => 'Receipt',
        'PaidBy' => 'Member',
        'SoldBy' => 'Member',
        'Member' => 'Member'
    );
	
	private static $defaults = array('Status' => 'Pending');

    private static $default_sort = "Created DESC";

    private static $searchable_fields = array(
    	'Created' => array(
			'field' => 'DateField',
			'filter' => 'DateMatchFilter'
		),
        'Member.Username',
        'Member.Surname',
        'Member.FirstName',
        'Price' => array(
            'filter' => 'GreaterThanOrEqualFilter'
        ),
        'BV' => array(
            'filter' => 'GreaterThanOrEqualFilter'
        ),
        'UpgradeGroupID',
        'Status'
    );

    private static $summary_fields = array(
    	'Created.Nice',
        'Member.Username',
        'Member.Name',
        'Title',
        'Price',
        'BV',
        'UpgradeGroup.TitleByLang',
        'Status.Title'
    );

    /**
     * Set order template
     *
     * @param $set_template string
     */
    static function set_template($set_template) {
        Config::inst()->update('OrderPackage', 'template', $set_template);
    }

    /**
     * Get order template
     *
     * @return string
     */
    static function get_template() {
        return Config::inst()->get('OrderPackage', 'template');
    }

    static function update_status($id, $status, $remark = false) {
        $order_package = OrderPackage::get()->byID($id);
        if(!$order_package || !$status) {
            return false;
        }

        $valid_status = $order_package->dbObject('Status')->enumValues();
        if($order_package->Status != $status && isset($valid_status[$status]) && $valid_status[$status]) {
            if($status == 'Fully Paid') {
                $order_package->PaidDate = SS_Datetime::now()->getValue();
				if($order_package->UpgradeGroupID){
                	$order_package->Member()->Groups()->add($order_package->UpgradeGroupID);
					$order_package->Member()->setField('MaxPayout', $order_package->Price * 3)->write();
				}
				if($order_package->Type == 'Register'){
					$order_package->Member()->sendRegisterEmail(array('PackageTitle' => $order_package->Title, 'PackagePrice' => $order_package->dbObject('Price')->Nice()));
				} else if($order_package->Type == 'Upgrade'){
					$order_package->Member()->sendUpgradeEmail(array('PackageTitle' => $order_package->Title, 'PackagePrice' => $order_package->dbObject('Price')->Nice()));
				}

                if($order_package->BV > 0 && $order_package->PaymentReceiptID) {
                    InvestProgram::create_program($order_package->ID);
                }

				if($order_package->Price > 0 && $order_package->PaymentReceiptID) {
					$promotion = array(
						'level1' => 0.2,
						'level2' => 0.2,
						'level3' => 0.3,
						'level4' => 0.3,
						'level5' => 0.4,
						'level6' => 0.5
					);
					
					if(isset($promotion[$order_package->UpgradeGroup()->Code])){
						$statement_data = array(
				            'Type' => 'Promotion',
				            'Credit' => $order_package->Price * $promotion[$order_package->UpgradeGroup()->Code],
				            'Reference' => $order_package->PaymentReceipt()->Reference,
				            'Description' => sprintf("PROMOTION %s FREE %s", date('m/Y'), DBField::create_field('Percentage', $promotion[$order_package->UpgradeGroup()->Code])->Nice())
				        );
						$id = TradeCoinAccount::create_statement($statement_data, $order_package->MemberID);
					}
                }

                $order_package->BatchID = BonusBatch::get_current_batch_id();
            } else if($status == 'Voided') {
                $order_package->VoidedDate = SS_Datetime::now()->getValue();
                if($order_package->UpgradeGroupID) {
                    $order_package->Member()->Groups()->removeByID($order_package->UpgradeGroupID);
                }

                if($program = InvestProgram::get()->find('OrderPackageID', $order_package->ID)) {
                    $program->IsClosed = 1;
                    $program->write();
                }
				
				if($order_package->BV > 0 && $order_package->PaymentReceiptID) {
                	$trade_coins = TradeCoinAccount::get()->filter('Type', 'Promotion')->filter('Reference', $order_package->PaymentReceipt()->Reference);
					foreach($trade_coins as $trade_coin){
						$statement_data = array(
				            'Type' => $trade_coin->Type,
				            'Debit' => $trade_coin->Credit,
				            'Reference' => $trade_coin->Reference,
				            'Description' => sprintf('Deduct - %s', $trade_coin->Description)
				        );
				        $id = TradeCoinAccount::create_statement($statement_data, $order_package->MemberID);
					}
                }
            }

            if($remark !== false) {
                $order_package->Remark = $remark;
            }

            $order_package->Status = $status;
            $order_package->extend('updateStatus', $status);
            $order_package->write();
        }
        return $order_package->ID;
    }

    function requireDefaultRecords() {
        if(!TransactionType::get()->find('Code', 'REGISTER')) {
            TransactionType::create()->setField('Code', 'REGISTER')->setField('Title', 'Registration')->setField('Description', 'Purchase register member package')->setField('Object', 'OrderPackage')->setField('Page', 'RegistrationPage')->setField('Action', 'complete')->write();
            DB::alteration_message('Register transaction type created', 'created');
        }

        if(!TransactionType::get()->find('Code', 'UPGRADE')) {
            TransactionType::create()->setField('Code', 'UPGRADE')->setField('Title', 'Upgrade')->setField('Description', 'Purchase upgrade member package')->setField('Object', 'OrderPackage')->setField('Page', 'UpgradePage')->setField('Action', 'complete')->write();
            DB::alteration_message('Upgrade transaction type created', 'created');
        }
		
		if(!TransactionType::get()->find('Code', 'REPURCHASE')) {
            TransactionType::create()->setField('Code', 'REPURCHASE')->setField('Title', 'Repurchase')->setField('Description', 'Re-Purchase member package')->setField('Object', 'OrderPackage')->setField('Page', 'PackageOrderPage')->setField('Action', '')->write();
            DB::alteration_message('Re-Purchase transaction type created', 'created');
        }
    }

    public function fieldLabels($includerelations = true) {
        $labels = parent::fieldLabels($includerelations);

		$labels['Created'] = _t('OrderPackage.ORDER_DATE', 'Order Date');
		$labels['Created.Nice'] = _t('OrderPackage.ORDER_DATE', 'Order Date');
        $labels['Type'] = _t('OrderPackage.TYPE', 'Type');
        $labels['Title'] = _t('OrderPackage.TITLE', 'Title');
        $labels['Price'] = _t('OrderPackage.PRICE', 'Price');
        $labels['BV'] = _t('OrderPackage.BV', 'BV');
        $labels['Status'] = _t('OrderPackage.STATUS', 'Status');
		$labels['Status.Title'] = _t('OrderPackage.STATUS', 'Status');
        $labels['PaidDate'] = _t('OrderPackage.PAID_DATE', 'Paid Date');
		$labels['PaidDate.Nice'] = _t('OrderPackage.PAID_DATE', 'Paid Date');
        $labels['VoidedDate'] = _t('OrderPackage.VOIDED_DATE', 'Voided Date');
		$labels['VoidedDate.Nice'] = _t('OrderPackage.VOIDED_DATE', 'Voided Date');
        $labels['Remark'] = _t('OrderPackage.REMARK', 'Remark');
        $labels['UpgradeGroup'] = _t('OrderPackage.UPGRADE_GROUP', 'Upgrade Group');
        $labels['UpgradeGroupID'] = _t('OrderPackage.UPGRADE_GROUP', 'Upgrade Group');
        $labels['UpgradeGroup.Title'] = _t('OrderPackage.UPGRADE_GROUP', 'Upgrade Group');
        $labels['UpgradeGroup.TitleByLang'] = _t('OrderPackage.UPGRADE_GROUP', 'Upgrade Group');
        $labels['Member.Username'] = _t('OrderPackage.USERNAME', 'Username');
        $labels['Member.Name'] = _t('OrderPackage.NAME', 'Name');
        $labels['Member.FirstName'] = _t('OrderPackage.FIRSTNAME', 'First Name');
        $labels['Member.Surname'] = _t('OrderPackage.SURNAME', 'Surname');
        $labels['PaidBy.Username'] = _t('OrderPackage.PAID_USERNAME', 'Paid Username');
        $labels['PaidBy.Name'] = _t('OrderPackage.PAID_NAME', 'Paid Name');
        $labels['PaidBy.FirstName'] = _t('OrderPackage.PAID_FIRSTNAME', 'Paid First Name');
        $labels['PaidBy.Surname'] = _t('OrderPackage.PAID_SURNAME', 'Paid Surname');
        $labels['SoldBy.Username'] = _t('OrderPackage.SOLD_USERNAME', 'Sold Username');
        $labels['SoldBy.Name'] = _t('OrderPackage.SOLD_NAME', 'Sold Name');
        $labels['SoldBy.FirstName'] = _t('OrderPackage.SOLD_FIRSTNAME', 'Sold First Name');
        $labels['SoldBy.Surname'] = _t('OrderPackage.SOLD_SURNAME', 'Sold Surname');

        return $labels;
    }

	function getDefaultSearchContext() {
		$search_context = parent::getDefaultSearchContext();
		$search_context->getSearchFields()->dataFieldByName('UpgradeGroupID')->setSource(Group::get()->filter('IsDistributorGroup', 1)->map('ID', 'TitleByLang')->toArray());
		return $search_context;
  	}

    function getCMSFields() {
        $fields = parent::getCMSFields();
        if($this->exists()) {
            $fields = FieldList::create(LiteralField::create('Statement', $this->ViewHTML()));
        }

        return $fields;
    }

    function Action() {
        $extra_action = '';
        foreach($this->PaymentReceipt()->Payments() as $payment) {
            if($action = $payment->getAction()) {
                $extra_action .= $action;
            }
        }
        $view_link = Controller::join_links(PackageOrderPage::get()->First()->Link('view_order'), $this->ID);
        $action = sprintf('<div class="btn-group"><button type="button" class="btn btn-default btn-sm dropdown-toggle" data-toggle="dropdown">%s <span class="caret"></span></button><ul class="dropdown-menu dropdown-menu-right"><li><a title="%s" data-title="%s" rel="popup" href="%s">%s</a></li>%s</ul></div>', _t('OrderPackage.ACTION', 'Action'), _t('OrderPackage.CLICK_VIEW_ORDER_DETAILS', 'Click here to view order details'), _t('OrderPackage.ORDER_DETAILS', 'Order Details'), $view_link, _t('OrderPackage.BUTTONVIEW', 'View'), $extra_action);

        return $action;
    }
	
	function getTitle() {
        return $this->Package()->Title;
    }
	
	function getStatusByLang(){
		if($this->Status){
			return _t(sprintf('%s.%s', 'OrderPackage', strtoupper(str_replace(' ', '_', $this->Status))), $this->Status);
		}
		
		return $this->Status;
	}

    function getFullDetailHTML() {
        Config::inst()->update('Currency', 'currency_symbol', '');
        $this->Format = 'HTML';
		$this->PaymentReceipt()->Format = 'HTML';
        $template = new SSViewer('OrderPackageDetail');
        $template->includeRequirements(false);
        return $this->renderWith($template);
    }

    function ViewHTML() {
        Config::inst()->update('Currency', 'currency_symbol', '');
        $template_ss = self::get_template();
        $this->PrintTime = SS_Datetime::now()->Nice();
        $this->Format = 'HTML';
		$this->PaymentReceipt()->Format = 'HTML';
        $this->SiteConfig = SiteConfig::current_site_config();
        $template = new SSViewer($template_ss);
        $template->includeRequirements(false);
        return $this->renderWith($template);
    }

    function ViewPDF() {
    	if($this->config()->allowed_pdf && class_exists('SS_DOMPDF')){
	        Config::inst()->update('Currency', 'currency_symbol', '');
	        $template_ss = self::get_template();
	        $this->PrintTime = SS_Datetime::now()->Nice();
	        $this->Format = 'PDF';
			$this->PaymentReceipt()->Format = 'PDF';
	        $this->SiteConfig = SiteConfig::current_site_config();
	        $template = new SSViewer($template_ss);
	        $template->includeRequirements(false);
	        $pdf = new SS_DOMPDF();
	        $pdf->setHTML($this->renderWith($template));
	        $pdf->render();
	        return $pdf->stream(sprintf('order_%s_%s.pdf', time(), $this->ID));
		}
    }

    function ViewPrint() {
        Config::inst()->update('Currency', 'currency_symbol', '');
        $template_ss = self::get_template();
        $this->PrintTime = SS_Datetime::now()->Nice();
        $this->Format = 'PRINT';
		$this->PaymentReceipt()->Format = 'PRINT';
        $this->SiteConfig = SiteConfig::current_site_config();
        $template = new SSViewer($template_ss);
        $template->includeRequirements(false);
        return $this->renderWith($template);
    }

    function canView($member = false) {
        $extended = $this->extendedCan(__FUNCTION__, $member);
        if($extended !== null) {
            return $extended;
        }
        return Permission::check('VIEW_OrderPackage');
    }

    function canEdit($member = false) {
        return false;
    }

    function canDelete($member = false) {
        return false;
    }

    function canCreate($member = false) {
        return false;
    }
	
	function canPrint($member = false) {
        $extended = $this->extendedCan(__FUNCTION__, $member);
        if($extended !== null) {
            return $extended;
        }
        return Permission::check('PRINT_OrderPackage');
    }
	
	function canApprove($member = false) {
        $extended = $this->extendedCan(__FUNCTION__, $member);
        if($extended !== null) {
            return $extended;
        }
        return Permission::check('APPROVE_OrderPackage') && $this->Status == 'Pending';
    }
	
	function canVoid($member = false) {
        $extended = $this->extendedCan(__FUNCTION__, $member);
        if($extended !== null) {
            return $extended;
        }
        return Permission::check('VOID_OrderPackage') && $this->Status != 'Voided';
    }

    function providePermissions() {
        return array(
            'VIEW_OrderPackage' => array(
                'name' => _t('OrderPackage.PERMISSION_VIEW', 'Allow view access right'),
                'category' => _t('OrderPackage.PERMISSIONS_CATEGORY', 'Order Package')
            ),
            'PRINT_OrderPackage' => array(
                'name' => _t('OrderPackage.PERMISSION_PRINT', 'Allow print access right'),
                'category' => _t('OrderPackage.PERMISSIONS_CATEGORY', 'Order Package')
            ),
            'APPROVE_OrderPackage' => array(
                'name' => _t('OrderPackage.PERMISSION_APPROVE', 'Allow approve access right'),
                'category' => _t('OrderPackage.PERMISSIONS_CATEGORY', 'Order Package')
            ),
            'VOID_OrderPackage' => array(
                'name' => _t('OrderPackage.PERMISSION_VOID', 'Allow void access right'),
                'category' => _t('OrderPackage.PERMISSIONS_CATEGORY', 'Order Package')
            )
        );
    }
}
?>
